package com.dd.shop4j.common.utils;

import java.io.IOException;
import java.math.BigInteger;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;

import javax.crypto.KeyGenerator;
import javax.crypto.Mac;
import javax.crypto.SecretKey;
import javax.crypto.spec.SecretKeySpec;

import org.apache.commons.lang.RandomStringUtils;

import sun.misc.BASE64Decoder;
import sun.misc.BASE64Encoder;

/**
 * 加密操作类
 * 
 * @author 唐恕
 * @version 1.0
 */
public abstract class EncryptUtils {

	public static final String MD5 = "MD5";
	public static final String SHA = "SHA";
	public static final String SHA256 = "SHA-256";
	public static final String SHA348 = "SHA-348";
	public static final String SHA512 = "SHA-512";
	
	public static final String HMACMD5 = "HmacMD5";
	public static final String HMACSHA = "HmacSHA1";
	public static final String HMACSHA256 = "HmacSHA256";
	public static final String HMACSHA348 = "HmacSHA384";
	public static final String HMACSHA512 = "HmacSHA512";
	
	
	/**
	 * BASE64加密
	 * 
	 * @param data
	 *            要加密的字符
	 * @return
	 */
	public static String encryptBASE64(String data) {
		return (new BASE64Encoder()).encodeBuffer(data.getBytes());
	}

	/**
	 * BASE64解密
	 * 
	 * @param data
	 *            要解密的字符
	 * @return
	 */
	public static String decryptBASE64(String data) {
		try {
			return new String((new BASE64Decoder()).decodeBuffer(data));
		} catch (IOException e) {
			e.printStackTrace();
		}
		return data;
	}

	/**
	 * MessageDigest加密
	 * 
	 * @param data
	 * @return
	 */
	public static String encrypt(String data, String encryptType) {
		MessageDigest md;
		try {
			md = MessageDigest.getInstance(encryptType);
			md.update(data.getBytes());
			byte[] b = md.digest();
			StringBuffer buf = new StringBuffer("");
			int i = 0;
			for (int offset = 0; offset < b.length; offset++) {
				i = b[offset];
				if (i < 0)
					i += 256;
				if (i < 16)
					buf.append("0");
				buf.append(Integer.toHexString(i));
			}
			return buf.toString();
		} catch (NoSuchAlgorithmException e) {
			return data;
		}
	}
	
	/**
	 * 默认MD5加密的时候
	 * @param data
	 * @return
	 */
	public static String encrypt(String data) {
		return encrypt(data, MD5);
	}

	/**
	 * MAC加密
	 * @param data
	 * @param macType
	 * @return
	 */
	public static String encryptMac(String data, String macType) {
		SecretKey secretKey = new SecretKeySpec(decryptBASE64(getMacKey()).getBytes(), macType);
		try {
			Mac mac = Mac.getInstance(secretKey.getAlgorithm());
			mac.init(secretKey);
			return new BigInteger(mac.doFinal(data.getBytes())).toString(16);
		} catch (Exception e) {
			return data;
		}
	}
	
	/**
	 * MAC默认加密
	 * @param data
	 * @param macType
	 * @return
	 */
	public static String encryptMac(String data) {
		return encryptMac(data, HMACMD5);
	}
	
	/**
	 * MAC密匙
	 * @return
	 */
	public static String getMacKey(String macType) {
		 try {
			KeyGenerator keyGenerator = KeyGenerator.getInstance(macType);
			SecretKey secretKey = keyGenerator.generateKey();
			return (new BASE64Encoder()).encodeBuffer(secretKey.getEncoded()).trim();   
		} catch (NoSuchAlgorithmException e) {
			return "";
		}
	}
	
	/**
	 * MAC默认密匙
	 * @return
	 */
	public static String getMacKey() {
		return getMacKey(HMACMD5);
	}
	
	@SuppressWarnings("static-access")
	public static String getUniqueKey() {
		return encrypt(new RandomStringUtils().randomNumeric(10) + System.currentTimeMillis(), SHA);
	}
	
	public static void main(String[] args) {
		//System.out.println(getMacKey(HMACMD5));
		//System.out.println(getMacKey(HMACSHA));
		//System.out.println(getMacKey(HMACSHA256));
		for (int i = 0; i < 10; i++)
			System.out.println(getMacKey(HMACSHA348));
		//System.out.println(getMacKey(HMACSHA512));
		
		//System.out.println(encrypt("123"));

		
//		for (int i = 0; i < 1000; i++) {
//			System.out.println(getUniqueKey());
//		}
	}
	
}






